#include "ProxySettingDlg.h"

#include <qbkernel/include/qb_base.h>
#include <qbnet/sock/socket_proxy_common.h>
#include <widgets/SCheckEx.h>

#include <QGridLayout>
#include <QLabel>
#include <QLineEdit>
#include <QPushButton>
#include <QVBoxLayout>

#include "../ServerInfo.h"
#include "../auth_mac.h"
#include "StartupDlg.h"

ProxySettingDlg::ProxySettingDlg(QWidget* p) : SPopupWindow(p) {
  setTitle(tr("代理设置"));

  QPushButton* confirmButton = addBtn(QMessageBox::Ok, tr("确定"));
  QPushButton* cancelButton = addBtn(QMessageBox::Cancel, tr("取消"));
  QPushButton* testLinkButton = addBtn(QMessageBox::Apply, tr("测试连接"));

  QVBoxLayout* mainLayout = contentLayout();
  mainLayout->addSpacing(8);

  QVBoxLayout* proxyMethodLayout = new QVBoxLayout();
  proxyMethodLayout->setContentsMargins(0, 0, 0, 0);
  proxyMethodLayout->setSpacing(8);
  mainLayout->addLayout(proxyMethodLayout);

  ProxyInfo proxy = QuoteServerInfo::instance().proxyInfo();

  m_noProxy = new SCheckEx(tr("不使用代理服务器"), this);
  m_noProxy->setSelectType(SCheckEx::SelectType::Radio);
  m_noProxy->setIndex(0);
  proxyMethodLayout->addWidget(m_noProxy);

  m_ownProxy = new SCheckEx(tr("使用如下代理服务器"), this);
  m_ownProxy->setSelectType(SCheckEx::SelectType::Radio);
  m_ownProxy->setIndex(1);
  proxyMethodLayout->addWidget(m_ownProxy);

  SRadioGroup* rg = new SRadioGroup(this);
  rg->addRadio(m_noProxy);
  rg->addRadio(m_ownProxy);

  proxyTypeLayout = new QGridLayout();
  proxyTypeLayout->setAlignment(Qt::AlignLeft);
  mainLayout->addLayout(proxyTypeLayout);
  proxyTypeLayout->setContentsMargins(16, 8, 0, 0);
  proxyTypeLayout->setSpacing(8);

  m_socket4 = new SCheckEx("Socks4", this);
  m_socket4->setFixedSize(200, 24);
  m_socket4->setIndex(10);
  m_socket4->setSelectType(SCheckEx::SelectType::Radio);
  proxyTypeLayout->addWidget(m_socket4, 0, 0);

  m_socket5 = new SCheckEx("Socks5", this);
  m_socket5->setFixedSize(200, 24);
  m_socket5->setIndex(11);
  m_socket5->setSelectType(SCheckEx::SelectType::Radio);
  proxyTypeLayout->addWidget(m_socket5, 0, 1);

  m_https = new SCheckEx("HTTPS", this);
  m_https->setFixedSize(200, 24);
  m_https->setIndex(12);
  m_https->setSelectType(SCheckEx::SelectType::Radio);
  proxyTypeLayout->addWidget(m_https, 1, 0);

  rg = new SRadioGroup(this);
  rg->addRadio(m_socket4);
  rg->addRadio(m_socket5);
  rg->addRadio(m_https);

  if (proxy.nProxyType == kProxyHttp) {
    m_https->setSelectState(Qt::Checked, false);
  } else if (proxy.nProxyType == kProxySocksVer4) {
    m_socket4->setSelectState(Qt::Checked, false);
  } else if (proxy.nProxyType == kProxySocksVer5) {
    m_socket5->setSelectState(Qt::Checked, false);
  }

  proxyAccountLayout = new QGridLayout();
  proxyAccountLayout->setContentsMargins(56, 8, 50, 0);
  proxyAccountLayout->setAlignment(Qt::AlignLeft);
  proxyAccountLayout->setVerticalSpacing(8);
  mainLayout->addLayout(proxyAccountLayout);

  m_address = new QLabel(tr("地 址:"), this);
  m_address->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Expanding);
  proxyAccountLayout->addWidget(m_address, 0, 0);

  m_editAddress = new QLineEdit(this);
  m_editAddress->setFixedSize(100, 24);
  proxyAccountLayout->addWidget(m_editAddress, 0, 1);
  if (!proxy.strProxyHost.empty())
    m_editAddress->setText(QString::fromStdString(proxy.strProxyHost));

  QWidget* dumyWidget = new QWidget();
  dumyWidget->setFixedSize(40, 24);
  proxyAccountLayout->addWidget(dumyWidget, 0, 2);

  m_port = new QLabel(tr("端 口:"), this);
  m_port->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Expanding);
  proxyAccountLayout->addWidget(m_port, 0, 3);

  m_editPort = new QLineEdit(this);
  m_editPort->setFixedSize(100, 24);
  proxyAccountLayout->addWidget(m_editPort, 0, 4);
  if (proxy.nProxyPort != 0) {
    std::string proxyPort = std::to_string(proxy.nProxyPort);
    m_editPort->setText(QString::fromStdString(proxyPort));
  }

  m_userName = new QLabel(tr("用户名:"), this);
  m_userName->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Expanding);
  proxyAccountLayout->addWidget(m_userName, 1, 0);

  m_editUserName = new QLineEdit(this);
  m_editUserName->setFixedSize(100, 24);
  proxyAccountLayout->addWidget(m_editUserName, 1, 1);
  if (!proxy.strUsername.empty())
    m_editUserName->setText(QString::fromStdString(proxy.strUsername));

  dumyWidget = new QWidget();
  dumyWidget->setFixedSize(40, 24);
  proxyAccountLayout->addWidget(dumyWidget, 1, 2);

  m_pwd = new QLabel(tr("密 码:"), this);
  m_pwd->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Expanding);
  proxyAccountLayout->addWidget(m_pwd, 1, 3);

  m_editPwd = new QLineEdit(this);
  m_editPwd->setFixedSize(100, 24);
  m_editPwd->setEchoMode(QLineEdit::Password);
  proxyAccountLayout->addWidget(m_editPwd, 1, 4);
  if (!proxy.strPassword.empty())
    m_editPwd->setText(QString::fromStdString(proxy.strPassword));

  mainLayout->addSpacing(8);

  QHBoxLayout* MacAddressLayout = new QHBoxLayout();
  MacAddressLayout->setContentsMargins(12, 10, 0, 0);

  mainLayout->addLayout(MacAddressLayout);

  m_labelMac = new QLabel(tr("Mac地址:"), this);
  m_labelMac->setStyleSheet("color:rgb(243,191,76)");
  MacAddressLayout->addWidget(m_labelMac);

  MacAddressLayout->setSpacing(15);

  QString strMac = getHostMacAddress();
  strMac = strMac.replace(QRegExp("\\:"), "-");
  m_LableMacAddress = new QLabel(strMac, this);
  m_LableMacAddress->setStyleSheet("color:rgb(243,191,76)");
  MacAddressLayout->addWidget(m_LableMacAddress);
  MacAddressLayout->addStretch();

  QVBoxLayout* reminderLayout = new QVBoxLayout();
  reminderLayout->setContentsMargins(15, 105, 0, 0);
  m_linkTestStr = new QLabel(tr(""), this);
  reminderLayout->addWidget(m_linkTestStr);
  mainLayout->addLayout(reminderLayout);

  enableProxy(proxy.nProxyType == 0);

  if (proxy.bUse) {
    m_ownProxy->setSelectState(Qt::Checked, false);
  } else {
    m_noProxy->setSelectState(Qt::Checked, false);
    onRadioStateChanged(0);
  }

  connect(m_noProxy, &SCheckEx::stateChanged, this,
          &ProxySettingDlg::onRadioStateChanged);
  connect(m_ownProxy, &SCheckEx::stateChanged, this,
          &ProxySettingDlg::onRadioStateChanged);
  connect(confirmButton, &QPushButton::clicked, this,
          &ProxySettingDlg::onClickConfirm);
  connect(cancelButton, &QPushButton::clicked, this, &QDialog::reject);
  connect(testLinkButton, &QPushButton::clicked, this,
          &ProxySettingDlg::onTestLink);
}

void ProxySettingDlg::onTestLink() {
  if (m_editAddress->text().isEmpty() || m_editPort->text().isEmpty()) {
    return;
  }

  std::string proxyIp = m_editAddress->text().toStdString();
  const char* proxyAddress = proxyIp.c_str();

  uint16_t proxyPort = atoi((char*)m_editPort->text().toStdString().c_str());

  std::string userName = m_editUserName->text().toStdString();
  const char* proxyUserName = userName.c_str();

  std::string proxyPassword = m_editPwd->text().toStdString();
  const char* proxyPwd = proxyPassword.c_str();

  ServerInfo currentServer = QuoteServerInfo::instance().currentServer();

  std::string destHost = currentServer.address;
  const char* destinationHost = destHost.c_str();

  QString destPort = QString::number(currentServer.port);
  uint16_t destinationPort = atoi((char*)destPort.toStdString().c_str());

  int32_t proxyType;

  if (m_noProxy->isSelected()) {
    proxyType = kProxyNone;
  } else if (m_ownProxy->isSelected()) {
    if (m_socket4->isSelected()) {
      proxyType = kProxySocksVer4;
    } else if (m_socket5->isSelected()) {
      proxyType = kProxySocksVer5;
    } else if (m_https->isSelected()) {
      proxyType = kProxyHttp;
    }
  }

  //	qb::qbBase::getNetworkService()->ProxyTest(proxyType, destinationHost,
  //destinationPort, proxyAddress, proxyPort, proxyUserName, proxyPwd, nullptr);
  int res = qb::qbBase::getNetworkService()->ProxyTest(
      proxyType, destinationHost, destinationPort, proxyAddress, proxyPort,
      proxyUserName, proxyPwd, nullptr);
  if (res == -1) {
    m_linkTestStr->setText(tr("Failed!"));
  } else {
    m_linkTestStr->setText(tr("Success Link!"));
  }
}

void ProxySettingDlg::onSaveProxy() {
  ProxyInfo proxy;
  proxy.strProxyHost = m_editAddress->text().toStdString();
  std::string poxyPort = m_editPort->text().toStdString();
  proxy.nProxyPort = atoi((char*)poxyPort.c_str());
  proxy.strUsername = m_editUserName->text().toStdString();
  proxy.strPassword = m_editPwd->text().toStdString();

  if (m_socket4->isSelected()) {
    proxy.nProxyType = kProxySocksVer4;
    proxy.bUse = true;
  } else if (m_socket5->isSelected()) {
    proxy.nProxyType = kProxySocksVer5;
    proxy.bUse = true;
  } else if (m_https->isSelected()) {
    proxy.nProxyType = kProxyHttp;
    proxy.bUse = true;
  }

  if (m_noProxy->isSelected() && proxy.nProxyType >= kProxyHttp) {
    proxy.bUse = false;
  }
  QuoteServerInfo::instance().updateProxyInfo(proxy);
}

void ProxySettingDlg::onClickConfirm() {
  onSaveProxy();
  QDialog::accept();
}

void ProxySettingDlg::onRadioStateChanged(int index) {
  enableProxy(m_noProxy->isSelected());
}

void ProxySettingDlg::enableProxy(bool enable) {
  m_socket4->setDisabled(enable);
  m_socket5->setDisabled(enable);
  m_https->setDisabled(enable);
  m_address->setDisabled(enable);
  m_editAddress->setDisabled(enable);
  m_port->setDisabled(enable);
  m_editPort->setDisabled(enable);
  m_userName->setDisabled(enable);
  m_editUserName->setDisabled(enable);
  m_pwd->setDisabled(enable);
  m_editPwd->setDisabled(enable);
}
